//*****************************************************************************
//
// boot_loader.h - This file contains the definitions and prototypes used by
//                 the example boot loader.
//
// Copyright (c) 2006-2007 Luminary Micro, Inc.  All rights reserved.
//
// Software License Agreement
//
// Luminary Micro, Inc. (LMI) is supplying this software for use solely and
// exclusively on LMI's microcontroller products.
//
// The software is owned by LMI and/or its suppliers, and is protected under
// applicable copyright laws.  All rights are reserved.  Any use in violation
// of the foregoing restrictions may subject the user to criminal sanctions
// under applicable laws, as well as to civil liability for the breach of the
// terms and conditions of this license.
//
// THIS SOFTWARE IS PROVIDED "AS IS".  NO WARRANTIES, WHETHER EXPRESS, IMPLIED
// OR STATUTORY, INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF
// MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE APPLY TO THIS SOFTWARE.
// LMI SHALL NOT, IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL, OR
// CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER.
//
// This is part of revision 323 of the Stellaris boot loader.
//
//*****************************************************************************

#ifndef __BOOT_LOADER_H__
#define __BOOT_LOADER_H__

//*****************************************************************************
//
//! \defgroup custom_defines Boot Loader Customization Defines
//!
//! There are several customization options available with the boot loader that
//! require no additional code but do allow enabling different interfaces and
//! options.  These include modifying the data transport options, changing
//! which GPIO pin and polarity of the pin that signal an update request, and
//! other miscellaneous settings.
//!
//! @{
//
//*****************************************************************************

//*****************************************************************************
//
//! This defines the crystal frequency used by the microcontroller running the
//! boot loader.  If this is unknown at the time of production, then use the
//! AUTOBAUD feature to properly configure the UART.
//
//*****************************************************************************
#define CRYSTAL_FREQ            6000000

//*****************************************************************************
//
//! Enable this to call a decryption routine during download of code to the
//! microcontroller.
//
//*****************************************************************************
#define ENABLE_DECRYPTION

//*****************************************************************************
//
//! If the boot loader is going to use the UART port for transmitting data,
//! then this define must be turned on.
//
//*****************************************************************************
#define UART_ENABLE_UPDATE

//*****************************************************************************
//
//! Enable this to allow automatically detect the baud rate when the crystal
//! value used in the system is unknown.  This requires that UART_ENABLE_UPDATE
//! also be defined.
//
//*****************************************************************************
//#define AUTOBAUD

//*****************************************************************************
//
//! If the boot loader is going to use the SSI port for transmitting data, then
//! this define must be enabled.
//
//*****************************************************************************
//#define SSI_ENABLE_UPDATE

//*****************************************************************************
//
//! This definition controls which GPIO port to use for checking boot
//! mode.
//
//*****************************************************************************
#define FORCED_UPDATE_PORT      (GPIO_PORTB_BASE)

//*****************************************************************************
//
//! This definition sets the GPIO pin in FORCED_UPDATE_PORT to use for checking
//! boot mode.  This is a zero-based number and the valid values are 0-7.
//
//*****************************************************************************
#define FORCED_UPDATE_PIN       (4)

//*****************************************************************************
//
//! This definition sets the level of the specified GPIO pin that causes the
//! boot loader to enter update mode.  If this value is set to 0, it indicates
//! that a low voltage level on the GPIO pin indicates an update request.  The
//! only other valid value is 1 indicating that a high voltage level indicates
//! an update request.
//
//*****************************************************************************
#define FORCED_UPDATE_POLARITY  (0)

//*****************************************************************************
//
//! This sets the start address of the application.  It is also used to detect
//! if the application at this address in the flash contains a valid
//! application.
//
//*****************************************************************************
#define APP_START_ADDRESS      (0x2000)

//*****************************************************************************
//
//! This defines the number of bytes reserved by the boot loader for stack
//! space.
//
//*****************************************************************************
#define STACK_SIZE             (64)

//*****************************************************************************
//
//! This defines the SSI chip select pin that is being used by the boot loader.
//
//*****************************************************************************
#define SSI_CS                  (GPIO_PIN_3)

//*****************************************************************************
//
//! This defines the SSI clock pin that is being used by the boot loader.
//
//*****************************************************************************
#define SSI_CLK                 (GPIO_PIN_2)

//*****************************************************************************
//
//! This defines the SSI transmit pin that is being used by the boot loader.
//
//*****************************************************************************
#define SSI_TX                  (GPIO_PIN_5)

//*****************************************************************************
//
//! This defines the SSI receive pin that is being used by the boot loader.
//
//*****************************************************************************
#define SSI_RX                  (GPIO_PIN_4)

//*****************************************************************************
//
//! This defines the combination of pins used to implement the SSI port used by
//! the boot loader.
//
//*****************************************************************************
#define SSI_PINS                (SSI_CLK | SSI_TX | SSI_RX | SSI_CS)


//*****************************************************************************
//
//! This defines the UART receive pin that is being used by the boot loader.
//
//*****************************************************************************
#define UART_RX                 (GPIO_PIN_0)

//*****************************************************************************
//
//! This defines the UART transmit pin that is being used by the boot loader.
//
//*****************************************************************************
#define UART_TX                 (GPIO_PIN_1)

//*****************************************************************************
//
//! This is the variable that is allocated to be used as the stack for the
//! boot loader.
//
//*****************************************************************************
extern unsigned long pulStack[STACK_SIZE];

//*****************************************************************************
//
// Close the Doxygen group.
//! @}
//
//*****************************************************************************

//*****************************************************************************
//
// Define the data transfer functions for either UART or SSI interfaces.
//
//*****************************************************************************
#ifdef UART_ENABLE_UPDATE

//*****************************************************************************
//
// UART Transport APIs
//
//*****************************************************************************
extern void UARTConfig(int iProcRatio);
extern int UARTSend(unsigned char const *pucData, unsigned char ucSize);
extern int UARTReceive(unsigned char *pucData, unsigned char ucSize);
int AutoBaud(unsigned int *pulRatio);

#define SendFunction    UARTSend
#define ReceiveFunction UARTReceive
#endif // ifdef UART_ENABLE_UPDATE

#ifdef SSI_ENABLE_UPDATE
//*****************************************************************************
//
// SSI Transport APIs
//
//*****************************************************************************
extern void SSIConfig(void);
extern int SendDataSSISlave(unsigned char const *pucData,
                            unsigned char ucSize);
extern int ReceiveDataSSISlave(unsigned char *pucData, unsigned char ucSize);

#define SendFunction    SendDataSSISlave
#define ReceiveFunction ReceiveDataSSISlave
#endif // ifdef SSI_ENABLE_UPDATE

//*****************************************************************************
//
//! \addtogroup main_loop
//! @{
//
//*****************************************************************************

//*****************************************************************************
//
//! This is the definition for the function used by the boot loader to send
//! data.  It should be set to the name of the function used to send data.
//
//*****************************************************************************
#define SendData            SendFunction

//*****************************************************************************
//
//! This is the definition for the function used by the boot loader to receive
//! data.  It should be set to the name of the function used to receive data.
//
//*****************************************************************************
#define ReceiveData         ReceiveFunction

//*****************************************************************************
//
//! This macro caculates the integer portion of the divisor used for generating
//! the baud rate for the UART.
//
//*****************************************************************************
#define UART_BAUD_INTEGER(ulBaud) (CRYSTAL_FREQ / (16 * ulBaud))

//*****************************************************************************
//
//! This macro caculates the fractional portion of the divisor used for
//! generating the baud rate for the UART.
//
//*****************************************************************************
#define UART_BAUD_FRACT(ulBaud)                                 \
    (((((CRYSTAL_FREQ % (16 * ulBaud)) * 8) / ulBaud) + 1) / 2)

//*****************************************************************************
//
//! This macro is used to generate a constant to represent the UART baud rate
//! to processor clock rate that is used by the UARTConfig() function.  This
//! prevents the need for run-time calculation of the ratio of baud rate to
//! processor clock rate.
//
//*****************************************************************************
#define UART_BAUD_RATIO(ulBaud)                                  \
    ((UART_BAUD_INTEGER(ulBaud) << 6) | UART_BAUD_FRACT(ulBaud))

//*****************************************************************************
//
// Close the Doxygen group.
//! @}
//
//*****************************************************************************

//*****************************************************************************
//
// Packet Handling APIs
//
//*****************************************************************************
int ReceivePacket(unsigned char *pucData, unsigned char *pucSize);
int SendPacket(unsigned char *pucData, unsigned char ucSize);
void AckPacket(void);
void NakPacket(void);

//*****************************************************************************
//
// General APIs
//
//*****************************************************************************
void CallApplication(unsigned long ulAddress);

#endif // __BOOT_LOADER_H__
